import React, { useState, useEffect, useMemo, useRef } from 'react';
import { createRoot } from 'react-dom/client';
import { 
  BookOpen, 
  Target, 
  Calendar, 
  LayoutDashboard, 
  Plus, 
  Search, 
  Save, 
  Trash2, 
  CheckCircle2, 
  Circle, 
  ChevronRight, 
  ChevronLeft,
  FileText,
  Link as LinkIcon,
  Folder,
  LogOut,
  Menu,
  X,
  Clock,
  Tag,
  Pencil,
  MoreVertical,
  CalendarDays,
  Hourglass,
  Home,
  Download,
  Upload,
  Settings,
  Database
} from 'lucide-react';

// --- Types ---

type Status = 'todo' | 'in-progress' | 'done';
type Priority = 'low' | 'medium' | 'high';

interface LearningLog {
  id: string;
  date: string;
  content: string;
  tags: string[];
  status: Status;
  timeSpent?: number; // minutes
}

// Updated Goal Interface for Hierarchy and Manual Progress
interface Goal {
  id: string;
  parentId: string | null; // For nesting
  title: string;
  description: string;
  deadline: string;
  priority: Priority;
  status: Status;
  manualProgress: number; // 0 to 100
  type: 'long-term' | 'short-term';
}

interface KnowledgeItem {
  id: string;
  title: string;
  category: string;
  type: 'link' | 'note' | 'file';
  content: string; // Description or Note Content or URL
  fileData?: string; // Base64 string for files
  fileName?: string; // Original filename
  tags: string[];
  addedAt: string;
}

interface CountdownItem {
  id: string;
  title: string;
  targetDate: string;
}

// --- Mock Initial Data ---

const INITIAL_LOGS: LearningLog[] = [
  { id: '1', date: new Date().toISOString(), content: '复习了 React Hooks 的用法，特别是 useEffect 的依赖数组陷阱。', tags: ['React', 'Frontend'], status: 'done', timeSpent: 60 },
];

const INITIAL_GOALS: Goal[] = [
  { 
    id: '1', 
    parentId: null,
    title: '精通 SQL 数据库', 
    description: '掌握高级查询优化、索引原理以及存储过程。', 
    deadline: '2024-12-31', 
    priority: 'high', 
    status: 'in-progress', 
    manualProgress: 35,
    type: 'long-term'
  },
  { 
    id: '2', 
    parentId: '1', // Child of SQL Goal
    title: '学习 Window Functions', 
    description: '理解 Rank, Dense_Rank, Row_Number 的区别', 
    deadline: '2024-10-15', 
    priority: 'medium', 
    status: 'todo', 
    manualProgress: 0,
    type: 'short-term'
  }
];

const INITIAL_KNOWLEDGE: KnowledgeItem[] = [
  { id: '1', title: 'SQL 优化指南', category: 'Database', type: 'link', content: 'https://use-the-index-luke.com/', tags: ['SQL', 'Performance'], addedAt: new Date().toISOString() },
];

const INITIAL_COUNTDOWNS: CountdownItem[] = [
  { id: '1', title: '期末考试', targetDate: '2024-12-20' },
  { id: '2', title: '雅思考试', targetDate: '2024-11-15' }
];

// --- Components ---

const Button = ({ children, onClick, variant = 'primary', className = '', icon: Icon, size = 'md' }: any) => {
  const baseStyle = "flex items-center justify-center rounded-lg transition-all duration-200 font-medium focus:outline-none focus:ring-2 focus:ring-offset-1";
  const sizes = {
    xs: "px-2 py-1 text-xs",
    sm: "px-3 py-1.5 text-xs",
    md: "px-4 py-2 text-sm"
  };
  const variants = {
    primary: "bg-slate-800 text-white hover:bg-slate-700 focus:ring-slate-800 shadow-sm",
    secondary: "bg-white text-slate-700 border border-slate-200 hover:bg-slate-50 focus:ring-slate-300 shadow-sm",
    danger: "bg-red-50 text-red-600 hover:bg-red-100 focus:ring-red-500",
    ghost: "bg-transparent text-slate-600 hover:bg-slate-100"
  };

  return (
    <button onClick={onClick} className={`${baseStyle} ${sizes[size as keyof typeof sizes]} ${variants[variant as keyof typeof variants]} ${className}`}>
      {Icon && <Icon size={size === 'xs' ? 12 : size === 'sm' ? 14 : 16} className={children ? "mr-2" : ""} />}
      {children}
    </button>
  );
};

const Card = ({ children, className = '' }: any) => (
  <div className={`bg-white rounded-xl shadow-sm border border-slate-100 p-6 ${className}`}>
    {children}
  </div>
);

const Badge = ({ children, color = 'blue' }: any) => {
  const colors = {
    blue: 'bg-blue-50 text-blue-700 border-blue-100',
    green: 'bg-green-50 text-green-700 border-green-100',
    yellow: 'bg-yellow-50 text-yellow-700 border-yellow-100',
    slate: 'bg-slate-100 text-slate-700 border-slate-200',
    red: 'bg-red-50 text-red-700 border-red-100',
  };
  return (
    <span className={`px-2.5 py-0.5 rounded-full text-xs font-medium border ${colors[color as keyof typeof colors]}`}>
      {children}
    </span>
  );
};

const ManualProgressBar = ({ progress, onChange, readOnly = false }: { progress: number, onChange?: (val: number) => void, readOnly?: boolean }) => {
  return (
    <div className="w-full">
      <div className="flex justify-between text-xs text-slate-500 mb-1.5">
        <span className="font-medium">当前进度</span>
        <span className="font-bold text-slate-700">{progress}%</span>
      </div>
      <div className="relative w-full h-3 bg-slate-100 rounded-full">
        <div 
          className="absolute top-0 left-0 h-full bg-gradient-to-r from-blue-400 to-blue-600 rounded-full transition-all duration-300" 
          style={{ width: `${progress}%`}}
        ></div>
        {!readOnly && (
           <input 
             type="range" 
             min="0" 
             max="100" 
             value={progress} 
             onChange={(e) => onChange && onChange(parseInt(e.target.value))}
             className="absolute inset-0 w-full h-full opacity-0 cursor-pointer"
             title="拖动调整进度"
           />
        )}
      </div>
    </div>
  );
};

// Reusable Goal Card with Sub-goal Overview
const GoalCard = ({ 
  goal, 
  allGoals, 
  onEnter, 
  onEdit, 
  onDelete, 
  onUpdateProgress,
  isCompact = false 
}: any) => {
  const children = allGoals.filter((g: Goal) => g.parentId === goal.id);
  const completedChildren = children.filter((g: Goal) => g.manualProgress === 100).length;
  
  return (
    <div 
      onClick={onEnter}
      className={`bg-white rounded-xl shadow-sm border border-slate-100 flex flex-col group hover:shadow-md hover:border-blue-200 transition-all cursor-pointer relative h-full ${isCompact ? 'p-5' : 'p-6'}`}
    >
        {/* Header: Title, Badges, Actions */}
        <div className="flex justify-between items-start mb-3">
            <div className="flex-1 mr-4 min-w-0">
                <h3 className="font-bold text-lg text-slate-800 truncate flex items-center">
                    {goal.title}
                </h3>
                <div className="flex gap-2 mt-2">
                    <Badge color={goal.type === 'long-term' ? 'blue' : 'green'}>{goal.type === 'long-term' ? '长期' : '短期'}</Badge>
                    <Badge color={goal.priority === 'high' ? 'red' : 'slate'}>{goal.priority === 'high' ? '高优' : goal.priority === 'medium' ? '中' : '低'}</Badge>
                </div>
            </div>
            {(onEdit || onDelete) && (
                <div className="flex gap-1 opacity-0 group-hover:opacity-100 transition-opacity bg-white pl-2">
                     {onEdit && <button onClick={(e) => { e.stopPropagation(); onEdit(goal); }} className="p-2 hover:bg-slate-100 rounded-full text-slate-400 hover:text-blue-600"><Pencil size={16} /></button>}
                     {onDelete && <button onClick={(e) => { e.stopPropagation(); onDelete(goal.id, e); }} className="p-2 hover:bg-slate-100 rounded-full text-slate-400 hover:text-red-500"><Trash2 size={16} /></button>}
                </div>
            )}
        </div>

        {/* Description */}
        <p className="text-slate-600 text-sm mb-4 line-clamp-2 h-10">{goal.description}</p>

        {/* Sub-goals Overview (New Feature) */}
        {children.length > 0 && (
            <div className="mb-4 bg-slate-50/80 rounded-lg p-3 border border-slate-100/50 text-sm" onClick={e => e.stopPropagation()}>
                <div className="flex justify-between items-center mb-2 text-xs text-slate-500 font-bold uppercase tracking-wider">
                    <span>子目标</span>
                    <span className="bg-slate-200 text-slate-600 px-1.5 py-0.5 rounded text-[10px]">{completedChildren}/{children.length}</span>
                </div>
                <div className="space-y-1.5">
                    {children.slice(0, 3).map((child: Goal) => (
                        <div key={child.id} className="flex items-center gap-2 truncate">
                            {child.manualProgress === 100 ? (
                                <CheckCircle2 size={14} className="text-green-500 shrink-0" />
                            ) : (
                                <Circle size={14} className="text-slate-300 shrink-0" />
                            )}
                            <span className={`truncate text-xs ${child.manualProgress === 100 ? 'text-slate-400 line-through' : 'text-slate-600'}`}>{child.title}</span>
                        </div>
                    ))}
                    {children.length > 3 && (
                        <div className="text-xs text-slate-400 pl-6">+ {children.length - 3} 个更多...</div>
                    )}
                </div>
            </div>
        )}

        {/* Progress Bar */}
        <div className="mt-auto" onClick={e => e.stopPropagation()}>
             <ManualProgressBar 
                progress={goal.manualProgress} 
                onChange={(val) => onUpdateProgress && onUpdateProgress(goal.id, val)}
             />
        </div>

        {/* Footer: Date & Enter Hint */}
        <div className="mt-4 flex justify-between items-center text-xs text-slate-400">
            <span>截止: {goal.deadline || '未设置'}</span>
            {onEnter && (
                <span className="flex items-center text-blue-500 font-medium group-hover:translate-x-1 transition-transform">
                    进入详情 <ChevronRight size={14} />
                </span>
            )}
        </div>
    </div>
  );
};

// --- Helper Functions ---

const getDaysLeft = (targetDate: string) => {
  if (!targetDate) return null;
  const target = new Date(targetDate);
  const now = new Date();
  target.setHours(0,0,0,0);
  now.setHours(0,0,0,0);
  const diffTime = target.getTime() - now.getTime();
  const diffDays = Math.ceil(diffTime / (1000 * 60 * 60 * 24));
  return diffDays;
};

// --- Modules ---

// 1. Dashboard Module
const Dashboard = ({ 
  logs, 
  goals, 
  countdowns, 
  setGoals,
  setCountdowns,
  onNavigateToGoal
}: { 
  logs: LearningLog[], 
  goals: Goal[], 
  countdowns: CountdownItem[],
  setGoals: any,
  setCountdowns: any,
  onNavigateToGoal: (id: string) => void
}) => {
  const rootGoals = goals.filter(g => !g.parentId && g.status !== 'done');
  const recentLogs = [...logs].sort((a, b) => new Date(b.date).getTime() - new Date(a.date).getTime()).slice(0, 3);
  
  const [isCountModalOpen, setIsCountModalOpen] = useState(false);
  const [newCountdown, setNewCountdown] = useState<Partial<CountdownItem>>({ title: '', targetDate: '' });

  const handleUpdateProgress = (goalId: string, newVal: number) => {
    setGoals(goals.map(g => g.id === goalId ? { ...g, manualProgress: newVal } : g));
  };

  const addCountdown = () => {
    if(!newCountdown.title || !newCountdown.targetDate) return;
    setCountdowns([...countdowns, { ...newCountdown, id: Date.now().toString() }]);
    setNewCountdown({ title: '', targetDate: '' });
    setIsCountModalOpen(false);
  }

  const deleteCountdown = (id: string) => {
      setCountdowns(countdowns.filter(c => c.id !== id));
  }

  return (
    <div className="space-y-8 animate-in fade-in duration-500">
      <header className="mb-6 flex justify-between items-end">
        <div>
          <h1 className="text-3xl font-bold text-slate-800">概览</h1>
          <p className="text-slate-500 mt-2">今天是 {new Date().toLocaleDateString(undefined, {year:'numeric', month:'long', day:'numeric', weekday:'long'})}</p>
        </div>
      </header>

      {/* Countdown Section */}
      <section>
        <div className="flex justify-between items-center mb-4">
           <h2 className="text-xl font-bold text-slate-800 flex items-center">
             <Hourglass size={20} className="mr-2 text-orange-500" />
             重要倒计时
           </h2>
           <Button size="xs" variant="ghost" onClick={() => setIsCountModalOpen(true)} icon={Plus}>添加</Button>
        </div>
        
        {isCountModalOpen && (
             <div className="fixed inset-0 z-50 flex items-center justify-center bg-black/20 backdrop-blur-sm p-4">
                 <Card className="w-full max-w-sm">
                     <h3 className="font-bold mb-4">添加倒计时</h3>
                     <input className="w-full mb-3 p-2 border rounded" placeholder="事件名称 (如: 期末考试)" value={newCountdown.title} onChange={e => setNewCountdown({...newCountdown, title: e.target.value})} />
                     <input type="date" className="w-full mb-4 p-2 border rounded" value={newCountdown.targetDate} onChange={e => setNewCountdown({...newCountdown, targetDate: e.target.value})} />
                     <div className="flex justify-end gap-2">
                         <Button size="sm" variant="ghost" onClick={() => setIsCountModalOpen(false)}>取消</Button>
                         <Button size="sm" onClick={addCountdown}>确定</Button>
                     </div>
                 </Card>
             </div>
        )}

        <div className="grid grid-cols-2 md:grid-cols-4 gap-4">
           {countdowns.length === 0 && (
               <div className="col-span-2 text-sm text-slate-400 italic py-2">没有正在倒计时的事件...</div>
           )}
           {countdowns.map(cd => {
               const days = getDaysLeft(cd.targetDate);
               const isUrgent = days !== null && days <= 7 && days >= 0;
               return (
                   <div key={cd.id} className={`group relative bg-white border rounded-xl p-4 shadow-sm flex flex-col items-center justify-center text-center ${isUrgent ? 'border-orange-200 bg-orange-50/30' : 'border-slate-100'}`}>
                       <button onClick={() => deleteCountdown(cd.id)} className="absolute top-2 right-2 opacity-0 group-hover:opacity-100 text-slate-400 hover:text-red-500 transition-opacity"><X size={14}/></button>
                       <div className="text-sm text-slate-500 mb-1">{cd.title}</div>
                       <div className={`text-3xl font-bold ${days !== null && days < 0 ? 'text-slate-400' : isUrgent ? 'text-orange-600' : 'text-slate-800'}`}>
                           {days !== null ? (days < 0 ? '已过' : days) : '-'}
                       </div>
                       <div className="text-xs text-slate-400 mt-1">{days !== null && days >= 0 ? '天剩余' : cd.targetDate}</div>
                   </div>
               )
           })}
        </div>
      </section>

      {/* Goal Overview Section */}
      <section>
        <div className="flex justify-between items-center mb-4">
          <h2 className="text-xl font-bold text-slate-800 flex items-center">
            <Target size={22} className="mr-2 text-blue-600" />
            核心目标进度
          </h2>
        </div>
        
        {rootGoals.length === 0 ? (
          <Card className="text-center py-10 border-dashed">
            <div className="text-slate-400 mb-2">当前没有进行中的主目标</div>
            <div className="text-sm text-slate-400">去“目标管理”添加一个吧！</div>
          </Card>
        ) : (
          <div className="grid grid-cols-1 md:grid-cols-2 gap-6">
            {rootGoals.map(goal => (
                <GoalCard 
                    key={goal.id} 
                    goal={goal} 
                    allGoals={goals} 
                    onUpdateProgress={handleUpdateProgress}
                    onEnter={() => onNavigateToGoal(goal.id)}
                />
            ))}
          </div>
        )}
      </section>

       {/* Recent Logs Section (Simplified) */}
       <section>
        <div className="flex justify-between items-center mb-4">
          <h2 className="text-xl font-bold text-slate-800 flex items-center">
            <BookOpen size={20} className="mr-2 text-green-600" />
            最近日记
          </h2>
        </div>
        <div className="space-y-3">
             {recentLogs.length === 0 ? <div className="text-slate-400 text-sm">暂无日记</div> : recentLogs.map(log => (
                 <div key={log.id} className="bg-white p-4 rounded-lg border border-slate-100 shadow-sm flex gap-4 items-start">
                     <div className="text-xs font-bold text-slate-400 whitespace-nowrap pt-1">{new Date(log.date).toLocaleDateString()}</div>
                     <div className="text-sm text-slate-700 line-clamp-2">{log.content}</div>
                 </div>
             ))}
        </div>
      </section>
    </div>
  );
};

// 2. Learning Diary Module
const DiaryModule = ({ logs, setLogs }: { logs: LearningLog[], setLogs: any }) => {
  const [content, setContent] = useState('');
  const [tags, setTags] = useState('');
  const [isAdding, setIsAdding] = useState(false);
  const [editingId, setEditingId] = useState<string | null>(null);

  const handleSubmit = () => {
    if (!content.trim()) return;

    if (editingId) {
      // Update existing
      const updatedLogs = logs.map(log => 
        log.id === editingId 
        ? { ...log, content, tags: tags.split(' ').filter(t => t) } 
        : log
      );
      setLogs(updatedLogs);
      setEditingId(null);
    } else {
      // Add new
      const newLog: LearningLog = {
        id: Date.now().toString(),
        date: new Date().toISOString(),
        content: content,
        tags: tags.split(' ').filter(t => t),
        status: 'done'
      };
      setLogs([newLog, ...logs]);
    }
    
    setContent('');
    setTags('');
    setIsAdding(false);
  };

  const handleEdit = (log: LearningLog) => {
    setContent(log.content);
    setTags(log.tags.join(' '));
    setEditingId(log.id);
    setIsAdding(true);
    window.scrollTo({ top: 0, behavior: 'smooth' });
  };

  const handleDelete = (id: string) => {
    if (confirm('确定要删除这条日记吗？')) {
      setLogs(logs.filter(l => l.id !== id));
      if (editingId === id) {
        setIsAdding(false);
        setEditingId(null);
        setContent('');
        setTags('');
      }
    }
  };

  const handleCancel = () => {
    setIsAdding(false);
    setEditingId(null);
    setContent('');
    setTags('');
  }

  const sortedLogs = useMemo(() => {
    return [...logs].sort((a, b) => new Date(b.date).getTime() - new Date(a.date).getTime());
  }, [logs]);

  return (
    <div className="space-y-6">
      <div className="flex justify-between items-center">
        <h2 className="text-2xl font-bold text-slate-800">每日学习日记</h2>
        <Button onClick={() => setIsAdding(!isAdding)} icon={isAdding ? X : Plus} variant={isAdding ? "ghost" : "primary"}>
           {isAdding ? "收起" : "写日记"}
        </Button>
      </div>

      {isAdding && (
        <Card className="animate-in fade-in slide-in-from-top-4 duration-300 border-blue-200 ring-4 ring-blue-50/50">
          <div className="flex justify-between items-center mb-4">
             <h3 className="text-lg font-bold text-slate-800">{editingId ? '编辑日记' : '今日学习打卡'}</h3>
             <span className="text-xs text-slate-400">{new Date().toLocaleDateString()}</span>
          </div>
          <textarea
            className="w-full p-4 border border-slate-200 rounded-lg focus:ring-2 focus:ring-blue-500 focus:outline-none min-h-[150px] text-slate-700 leading-relaxed resize-none"
            placeholder="今天学了什么？解决了什么Bug？有什么心得？..."
            value={content}
            onChange={(e) => setContent(e.target.value)}
          />
          <div className="mt-4 flex flex-col md:flex-row items-center gap-4">
            <div className="relative flex-1 w-full">
               <Tag size={16} className="absolute left-3 top-1/2 -translate-y-1/2 text-slate-400"/>
               <input
                type="text"
                className="w-full pl-9 p-2 border border-slate-200 rounded-lg focus:outline-none focus:border-blue-500"
                placeholder="标签 (空格分隔，如: SQL 算法)"
                value={tags}
                onChange={(e) => setTags(e.target.value)}
              />
            </div>
            <div className="flex gap-2 w-full md:w-auto">
               <Button onClick={handleCancel} variant="ghost" className="flex-1 md:flex-none">取消</Button>
               <Button onClick={handleSubmit} className="flex-1 md:flex-none">{editingId ? '更新记录' : '发布日记'}</Button>
            </div>
          </div>
        </Card>
      )}

      <div className="space-y-8">
        {sortedLogs.map((log, index) => {
          const showDateHeader = index === 0 || new Date(log.date).toLocaleDateString() !== new Date(sortedLogs[index - 1].date).toLocaleDateString();
          return (
            <div key={log.id}>
              {showDateHeader && (
                <div className="flex items-center gap-2 mb-4 mt-8">
                   <CalendarDays size={18} className="text-slate-400" />
                   <h3 className="text-sm font-bold text-slate-500 bg-slate-100 px-3 py-1 rounded-full">{new Date(log.date).toLocaleDateString(undefined, {weekday: 'long', year: 'numeric', month: 'long', day: 'numeric'})}</h3>
                </div>
              )}
              
              <div className="relative pl-6 ml-3 border-l-2 border-slate-200 pb-2 group">
                 <div className="absolute -left-[9px] top-1 w-4 h-4 rounded-full border-2 border-white bg-blue-400 shadow-sm"></div>
                 
                 <div className="bg-white rounded-lg p-4 border border-slate-100 shadow-sm hover:shadow-md transition-all">
                    <div className="flex justify-between items-start mb-2">
                       <span className="text-xs font-mono text-slate-400">{new Date(log.date).toLocaleTimeString([], {hour: '2-digit', minute:'2-digit'})}</span>
                       <div className="flex gap-1 opacity-0 group-hover:opacity-100 transition-opacity">
                          <Button variant="ghost" size="sm" onClick={() => handleEdit(log)} icon={Pencil} />
                          <Button variant="ghost" size="sm" onClick={() => handleDelete(log.id)} icon={Trash2} className="text-red-400 hover:text-red-600" />
                       </div>
                    </div>
                    <p className="text-slate-700 whitespace-pre-wrap leading-relaxed">{log.content}</p>
                    {log.tags.length > 0 && (
                      <div className="flex flex-wrap gap-2 mt-3 pt-3 border-t border-slate-50">
                        {log.tags.map(t => <span key={t} className="text-xs text-blue-600 bg-blue-50 px-2 py-0.5 rounded">#{t}</span>)}
                      </div>
                    )}
                 </div>
              </div>
            </div>
          );
        })}
      </div>
    </div>
  );
};

// 3. Goal Management Module (Refactored for Hierarchy & Manual Progress)
const GoalsModule = ({ 
    goals, 
    setGoals, 
    currentParentId, 
    setCurrentParentId 
}: { 
    goals: Goal[], 
    setGoals: any, 
    currentParentId: string | null, 
    setCurrentParentId: (id: string | null) => void 
}) => {
  const [isModalOpen, setIsModalOpen] = useState(false);
  const [editingGoal, setEditingGoal] = useState<Goal | null>(null);
  const [newGoal, setNewGoal] = useState<Partial<Goal>>({ title: '', description: '', priority: 'medium', type: 'short-term', deadline: '', manualProgress: 0 });

  // Navigation Logic
  const currentLevelGoals = goals.filter(g => g.parentId === currentParentId);
  const currentParentGoal = goals.find(g => g.id === currentParentId);

  // Breadcrumb generation
  const getBreadcrumbs = () => {
    const crumbs = [];
    let curr = currentParentGoal;
    while(curr) {
      crumbs.unshift(curr);
      curr = goals.find(g => g.id === curr?.parentId);
    }
    return crumbs;
  };

  const breadcrumbs = getBreadcrumbs();

  const openModal = (goal?: Goal) => {
    if (goal) {
      setEditingGoal(goal);
      setNewGoal({ ...goal });
    } else {
      setEditingGoal(null);
      setNewGoal({ 
          title: '', 
          description: '', 
          priority: 'medium', 
          type: 'short-term', 
          deadline: '', 
          manualProgress: 0,
          parentId: currentParentId 
      });
    }
    setIsModalOpen(true);
  };

  const handleSaveGoal = () => {
    if (!newGoal.title) return;

    if (editingGoal) {
      const updated = goals.map(g => g.id === editingGoal.id ? { ...g, ...newGoal } as Goal : g);
      setGoals(updated);
    } else {
      const goal: Goal = {
        id: Date.now().toString(),
        parentId: currentParentId,
        title: newGoal.title!,
        description: newGoal.description || '',
        deadline: newGoal.deadline || '',
        priority: (newGoal.priority as Priority) || 'medium',
        type: (newGoal.type as any) || 'short-term',
        status: 'todo',
        manualProgress: newGoal.manualProgress || 0
      };
      setGoals([...goals, goal]);
    }
    setIsModalOpen(false);
  };

  const deleteGoal = (id: string, e: React.MouseEvent) => {
      e.stopPropagation();
      const getAllChildrenIds = (parentId: string): string[] => {
          const children = goals.filter(g => g.parentId === parentId);
          let ids = children.map(c => c.id);
          children.forEach(c => ids = [...ids, ...getAllChildrenIds(c.id)]);
          return ids;
      };

      if(confirm('删除此目标将同时删除其下所有子目标，确定吗？')) {
        const idsToDelete = [id, ...getAllChildrenIds(id)];
        setGoals(goals.filter(g => !idsToDelete.includes(g.id)));
      }
  }

  const handleUpdateProgress = (id: string, val: number) => {
      setGoals(goals.map(g => g.id === id ? { ...g, manualProgress: val } : g));
  }

  return (
    <div className="space-y-6">
      
      {/* Navigation Header */}
      <div className="flex flex-col gap-4">
          <div className="flex justify-between items-center">
            <h2 className="text-2xl font-bold text-slate-800">目标管理</h2>
            <Button onClick={() => openModal()} icon={Plus}>
                {currentParentId ? '添加子目标' : '新目标'}
            </Button>
          </div>

          {/* Breadcrumbs */}
          <div className="flex items-center gap-2 text-sm text-slate-500 overflow-x-auto pb-2">
             <button 
                onClick={() => setCurrentParentId(null)} 
                className={`flex items-center hover:text-blue-600 transition-colors ${!currentParentId ? 'font-bold text-slate-800' : ''}`}
             >
                <Home size={14} className="mr-1"/> 全部目标
             </button>
             {breadcrumbs.map(crumb => (
                 <React.Fragment key={crumb.id}>
                    <ChevronRight size={14} className="text-slate-300 flex-shrink-0" />
                    <button 
                        onClick={() => setCurrentParentId(crumb.id)}
                        className={`hover:text-blue-600 transition-colors whitespace-nowrap ${currentParentId === crumb.id ? 'font-bold text-slate-800' : ''}`}
                    >
                        {crumb.title}
                    </button>
                 </React.Fragment>
             ))}
          </div>

          {/* Parent Goal Details (If inside a goal) */}
          {currentParentGoal && (
             <Card className="bg-blue-50/50 border-blue-100">
                <div className="flex justify-between items-start mb-4">
                    <div>
                        <h3 className="text-xl font-bold text-slate-800 mb-2">{currentParentGoal.title}</h3>
                        <p className="text-slate-600">{currentParentGoal.description || '无描述'}</p>
                    </div>
                    <Button size="sm" variant="secondary" icon={Pencil} onClick={() => openModal(currentParentGoal)}>编辑详情</Button>
                </div>
                <div className="bg-white p-4 rounded-lg border border-blue-100">
                     <ManualProgressBar 
                        progress={currentParentGoal.manualProgress} 
                        onChange={(val) => handleUpdateProgress(currentParentGoal.id, val)}
                     />
                </div>
             </Card>
          )}
      </div>

      {isModalOpen && (
        <div className="fixed inset-0 bg-slate-900/50 backdrop-blur-sm flex items-center justify-center z-50 p-4">
          <Card className="w-full max-w-lg max-h-[90vh] overflow-y-auto animate-in zoom-in-95 duration-200">
            <div className="flex justify-between items-center mb-6">
              <h3 className="text-xl font-bold text-slate-800">{editingGoal ? '编辑目标' : '新建目标'}</h3>
              <button onClick={() => setIsModalOpen(false)} className="text-slate-400 hover:text-slate-600"><X size={24} /></button>
            </div>
            
            <div className="space-y-4">
              <div>
                <label className="block text-sm font-medium text-slate-700 mb-1">目标标题</label>
                <input 
                  className="w-full p-2.5 border border-slate-200 rounded-lg focus:ring-2 focus:ring-blue-500 focus:outline-none" 
                  placeholder="例如: 学会 Python" 
                  value={newGoal.title} 
                  onChange={e => setNewGoal({...newGoal, title: e.target.value})} 
                />
              </div>
              
              <div>
                <label className="block text-sm font-medium text-slate-700 mb-1">描述</label>
                <textarea 
                  className="w-full p-2.5 border border-slate-200 rounded-lg h-24 focus:ring-2 focus:ring-blue-500 focus:outline-none resize-none" 
                  placeholder="详细描述..." 
                  value={newGoal.description} 
                  onChange={e => setNewGoal({...newGoal, description: e.target.value})} 
                />
              </div>

              <div className="grid grid-cols-2 gap-4">
                <div>
                   <label className="block text-sm font-medium text-slate-700 mb-1">优先级</label>
                   <select 
                      className="w-full p-2.5 border border-slate-200 rounded-lg bg-white" 
                      value={newGoal.priority} 
                      onChange={e => setNewGoal({...newGoal, priority: e.target.value as Priority})}
                    >
                      <option value="low">低</option>
                      <option value="medium">中</option>
                      <option value="high">高</option>
                    </select>
                </div>
                <div>
                   <label className="block text-sm font-medium text-slate-700 mb-1">类型</label>
                   <select 
                      className="w-full p-2.5 border border-slate-200 rounded-lg bg-white" 
                      value={newGoal.type} 
                      onChange={e => setNewGoal({...newGoal, type: e.target.value as any})}
                    >
                      <option value="short-term">短期目标</option>
                      <option value="long-term">长期目标</option>
                    </select>
                </div>
              </div>
              
              <div>
                <label className="block text-sm font-medium text-slate-700 mb-1">截止日期</label>
                <input 
                  type="date" 
                  className="w-full p-2.5 border border-slate-200 rounded-lg"
                  value={newGoal.deadline}
                  onChange={e => setNewGoal({...newGoal, deadline: e.target.value})}
                />
              </div>

              {!editingGoal && (
                 <div>
                    <label className="block text-sm font-medium text-slate-700 mb-1">初始进度</label>
                    <input 
                       type="range" min="0" max="100" 
                       className="w-full"
                       value={newGoal.manualProgress}
                       onChange={e => setNewGoal({...newGoal, manualProgress: parseInt(e.target.value)})}
                    />
                    <div className="text-right text-xs text-slate-500">{newGoal.manualProgress}%</div>
                 </div>
              )}

              <div className="flex justify-end gap-3 mt-8">
                <Button variant="ghost" onClick={() => setIsModalOpen(false)}>取消</Button>
                <Button onClick={handleSaveGoal}>保存</Button>
              </div>
            </div>
          </Card>
        </div>
      )}

      {/* Goal List */}
      <div className="grid grid-cols-1 md:grid-cols-2 gap-6">
        {currentLevelGoals.length === 0 ? (
            <div className="col-span-full text-center py-12 bg-slate-50 rounded-xl border border-dashed border-slate-200">
                <p className="text-slate-400">
                    {currentParentId ? "该目标下还没有细分的子目标" : "还没有建立目标"}
                </p>
                <Button variant="ghost" className="mt-2 text-blue-500" onClick={() => openModal()}>立即添加</Button>
            </div>
        ) : (
            currentLevelGoals.map(goal => (
                <GoalCard 
                    key={goal.id}
                    goal={goal}
                    allGoals={goals}
                    onUpdateProgress={handleUpdateProgress}
                    onEnter={() => setCurrentParentId(goal.id)}
                    onEdit={openModal}
                    onDelete={deleteGoal}
                />
            ))
        )}
      </div>
    </div>
  );
};

// 4. Knowledge Base Module
const KnowledgeModule = ({ knowledge, setKnowledge }: { knowledge: KnowledgeItem[], setKnowledge: any }) => {
  const [searchTerm, setSearchTerm] = useState('');
  const [categoryFilter, setCategoryFilter] = useState('All');
  const [isModalOpen, setIsModalOpen] = useState(false);
  const [editingId, setEditingId] = useState<string | null>(null);
  
  const [newItem, setNewItem] = useState<Partial<KnowledgeItem>>({ type: 'link', category: 'General' });

  const categories = ['All', ...Array.from(new Set(knowledge.map(k => k.category)))];

  const filteredKnowledge = knowledge.filter(k => {
    const matchesSearch = k.title.toLowerCase().includes(searchTerm.toLowerCase()) || k.tags.some(t => t.toLowerCase().includes(searchTerm.toLowerCase()));
    const matchesCategory = categoryFilter === 'All' || k.category === categoryFilter;
    return matchesSearch && matchesCategory;
  });

  const openModal = (item?: KnowledgeItem) => {
      if (item) {
          setEditingId(item.id);
          setNewItem({
              ...item, 
              tags: item.tags.join(' ') as any,
              fileData: item.fileData,
              fileName: item.fileName
          });
      } else {
          setEditingId(null);
          setNewItem({ 
              type: 'link', 
              category: 'General', 
              title: '', 
              content: '', 
              tags: '' as any,
              fileData: undefined,
              fileName: undefined
          });
      }
      setIsModalOpen(true);
  }

  const handleFileChange = (e: React.ChangeEvent<HTMLInputElement>) => {
    const file = e.target.files?.[0];
    if (file) {
      if (file.size > 3 * 1024 * 1024) {
          alert("温馨提示：由于浏览器本地存储限制，建议上传小于 3MB 的文件，否则可能保存失败。");
      }
      const reader = new FileReader();
      reader.onloadend = () => {
        setNewItem(prev => ({
            ...prev,
            fileData: reader.result as string,
            fileName: file.name
        }));
      };
      reader.readAsDataURL(file);
    }
  };

  const handleSave = () => {
    if (!newItem.title) return;
    
    // For files, content is optional or used as description
    if (newItem.type !== 'file' && !newItem.content) return; 

    const tagsInput = newItem.tags as any;
    const tagsArray = typeof tagsInput === 'string' ? tagsInput.split(' ').filter((t: string) => t) : tagsInput;

    if (editingId) {
        const updated = knowledge.map(k => k.id === editingId ? { ...k, ...newItem, tags: tagsArray } as KnowledgeItem : k);
        setKnowledge(updated);
    } else {
        const item: KnowledgeItem = {
            id: Date.now().toString(),
            title: newItem.title!,
            content: newItem.content || '',
            category: newItem.category || 'General',
            type: newItem.type as any,
            tags: tagsArray as any,
            addedAt: new Date().toISOString(),
            fileData: newItem.fileData,
            fileName: newItem.fileName
        };
        setKnowledge([...knowledge, item]);
    }
    setIsModalOpen(false);
  }

  const handleDelete = (id: string) => {
      if(confirm('确定删除此条目吗？')) setKnowledge(knowledge.filter(k => k.id !== id));
  }

  return (
    <div className="space-y-6">
      <div className="flex flex-col md:flex-row justify-between md:items-center gap-4">
        <h2 className="text-2xl font-bold text-slate-800">个人知识库</h2>
        <div className="flex gap-2">
           <div className="relative">
             <Search size={18} className="absolute left-3 top-1/2 -translate-y-1/2 text-slate-400" />
             <input 
                type="text" 
                placeholder="搜索标题、标签..." 
                className="pl-10 pr-4 py-2 border rounded-lg focus:outline-none focus:ring-2 focus:ring-blue-100 w-full md:w-64"
                value={searchTerm}
                onChange={e => setSearchTerm(e.target.value)}
             />
           </div>
           <Button onClick={() => openModal()} icon={Plus}>添加资源</Button>
        </div>
      </div>

      <div className="flex gap-2 overflow-x-auto pb-2 scrollbar-hide">
        {categories.map(cat => (
          <button
            key={cat}
            onClick={() => setCategoryFilter(cat)}
            className={`px-4 py-1.5 rounded-full text-sm whitespace-nowrap transition-colors border ${
              categoryFilter === cat ? 'bg-slate-800 text-white border-slate-800' : 'bg-white text-slate-600 hover:bg-slate-100 border-slate-200'
            }`}
          >
            {cat}
          </button>
        ))}
      </div>

      {isModalOpen && (
        <div className="fixed inset-0 bg-slate-900/50 backdrop-blur-sm flex items-center justify-center z-50 p-4">
          <Card className="w-full max-w-lg animate-in zoom-in-95 duration-200">
             <div className="flex justify-between items-center mb-4">
                 <h3 className="font-bold text-slate-800">{editingId ? '编辑资源' : '添加新资源'}</h3>
                 <button onClick={() => setIsModalOpen(false)}><X size={20} className="text-slate-400" /></button>
             </div>
             
             <div className="grid grid-cols-1 md:grid-cols-2 gap-4">
                 <div>
                    <label className="text-xs font-bold text-slate-500 mb-1 block">标题</label>
                    <input className="w-full p-2 border rounded" placeholder="标题" value={newItem.title || ''} onChange={e => setNewItem({...newItem, title: e.target.value})} />
                 </div>
                 <div>
                    <label className="text-xs font-bold text-slate-500 mb-1 block">分类</label>
                    <input className="w-full p-2 border rounded" placeholder="例如: React" value={newItem.category || ''} onChange={e => setNewItem({...newItem, category: e.target.value})} />
                 </div>
                 <div>
                    <label className="text-xs font-bold text-slate-500 mb-1 block">类型</label>
                    <select className="w-full p-2 border rounded bg-white" value={newItem.type} onChange={e => setNewItem({...newItem, type: e.target.value as any})}>
                        <option value="link">链接 (Link)</option>
                        <option value="note">笔记 (Note)</option>
                        <option value="file">文件 (File Upload)</option>
                    </select>
                 </div>
                 <div>
                    <label className="text-xs font-bold text-slate-500 mb-1 block">标签</label>
                    <input className="w-full p-2 border rounded" placeholder="空格分隔" value={(newItem.tags as any) || ''} onChange={e => setNewItem({...newItem, tags: e.target.value as any})} />
                 </div>
             </div>
             
             <div className="mt-4">
                {newItem.type === 'file' ? (
                    <div>
                        <label className="text-xs font-bold text-slate-500 mb-1 block">上传文件</label>
                        <div className="flex items-center gap-2 mb-3">
                             <label className="cursor-pointer bg-slate-100 hover:bg-slate-200 text-slate-600 px-4 py-2 rounded-lg text-sm flex items-center transition-colors border border-slate-200">
                                 <Upload size={16} className="mr-2"/> 
                                 <input type="file" className="hidden" onChange={handleFileChange} />
                                 选择文件
                             </label>
                             <span className="text-sm text-slate-500 truncate max-w-[200px]">
                                 {newItem.fileName || '未选择文件'}
                             </span>
                        </div>
                        <label className="text-xs font-bold text-slate-500 mb-1 block">备注 / 描述 (选填)</label>
                        <textarea 
                            className="w-full p-2 border rounded h-20 resize-none" 
                            placeholder="关于此文件的描述..."
                            value={newItem.content || ''}
                            onChange={e => setNewItem({...newItem, content: e.target.value})}
                        />
                    </div>
                ) : (
                    <div>
                        <label className="text-xs font-bold text-slate-500 mb-1 block">{newItem.type === 'link' ? "链接 URL" : "笔记内容"}</label>
                        <textarea 
                            className="w-full p-2 border rounded h-32 resize-none" 
                            placeholder={newItem.type === 'link' ? "输入 https://..." : "输入笔记内容..."}
                            value={newItem.content || ''}
                            onChange={e => setNewItem({...newItem, content: e.target.value})}
                        />
                    </div>
                )}
             </div>
             
             <div className="flex justify-end gap-3 mt-4">
                 <Button variant="ghost" onClick={() => setIsModalOpen(false)}>取消</Button>
                 <Button onClick={handleSave}>保存</Button>
             </div>
          </Card>
        </div>
      )}

      <div className="grid grid-cols-1 md:grid-cols-2 lg:grid-cols-3 gap-6">
        {filteredKnowledge.map(item => (
          <div key={item.id} className="bg-white rounded-xl p-5 shadow-sm border border-slate-100 hover:shadow-md transition-shadow relative group flex flex-col h-full">
            <div className="absolute top-3 right-3 flex gap-1 opacity-0 group-hover:opacity-100 transition-all bg-white pl-2">
                <button onClick={() => openModal(item)} className="p-1 text-slate-400 hover:text-blue-500"><Pencil size={14} /></button>
                <button onClick={() => handleDelete(item.id)} className="p-1 text-slate-400 hover:text-red-500"><Trash2 size={14} /></button>
            </div>
            
            <div className="flex items-center mb-3 pr-10">
               <div className={`p-2 rounded-lg mr-3 shrink-0 ${item.type === 'link' ? 'bg-blue-100 text-blue-600' : item.type === 'note' ? 'bg-yellow-100 text-yellow-600' : 'bg-green-100 text-green-600'}`}>
                  {item.type === 'link' ? <LinkIcon size={18} /> : item.type === 'note' ? <FileText size={18} /> : <Folder size={18} />}
               </div>
               <div className="min-w-0">
                   <h4 className="font-bold text-slate-800 truncate" title={item.title}>{item.title}</h4>
                   <span className="text-xs text-slate-500">{item.category}</span>
               </div>
            </div>
            
            <div className="text-sm text-slate-600 mb-4 flex-1">
                 {item.type === 'link' ? (
                     <a href={item.content} target="_blank" rel="noopener noreferrer" className="text-blue-500 hover:underline break-all line-clamp-3">{item.content}</a>
                 ) : item.type === 'file' ? (
                     <div>
                        <p className="text-sm text-slate-600 mb-3 line-clamp-2">{item.content || '无描述'}</p>
                        <div className="bg-slate-50 border border-slate-200 rounded-lg p-3 flex items-center justify-between group/file hover:border-blue-300 transition-colors">
                             <div className="flex items-center gap-2 overflow-hidden">
                                 <div className="bg-white p-1.5 rounded border border-slate-200">
                                    <FileText size={16} className="text-slate-500" />
                                 </div>
                                 <span className="text-sm text-slate-700 truncate font-medium">{item.fileName || 'Unknown File'}</span>
                             </div>
                             {item.fileData && (
                                 <a 
                                    href={item.fileData} 
                                    download={item.fileName || 'download'}
                                    className="p-2 text-slate-400 hover:text-blue-600 hover:bg-white rounded-full transition-all"
                                    title="下载文件"
                                 >
                                    <Download size={18} />
                                 </a>
                             )}
                        </div>
                     </div>
                 ) : (
                     <p className="line-clamp-3 whitespace-pre-wrap">{item.content}</p>
                 )}
            </div>
            
            <div className="flex flex-wrap gap-2 mt-auto pt-3 border-t border-slate-50">
                {item.tags.map(tag => <span key={tag} className="text-[10px] bg-slate-50 text-slate-500 px-2 py-0.5 rounded border border-slate-100">#{tag}</span>)}
            </div>
          </div>
        ))}
      </div>
    </div>
  );
};

// --- Main App Component ---

const App = () => {
  const [isAuthenticated, setIsAuthenticated] = useState(false);
  const [passwordInput, setPasswordInput] = useState('');
  const [activeTab, setActiveTab] = useState<'dashboard' | 'logs' | 'goals' | 'knowledge'>('dashboard');
  const [isMobileMenuOpen, setIsMobileMenuOpen] = useState(false);
  
  // Settings/Backup Modal State
  const [isDataModalOpen, setIsDataModalOpen] = useState(false);

  // Persistence State
  const [logs, setLogs] = useState<LearningLog[]>([]);
  const [goals, setGoals] = useState<Goal[]>([]);
  const [knowledge, setKnowledge] = useState<KnowledgeItem[]>([]);
  const [countdowns, setCountdowns] = useState<CountdownItem[]>([]);
  
  // Navigation State (Lifted Up)
  const [currentParentId, setCurrentParentId] = useState<string | null>(null);

  // Load Data
  useEffect(() => {
    const loadedLogs = localStorage.getItem('my_growth_logs');
    const loadedGoals = localStorage.getItem('my_growth_goals');
    const loadedKnow = localStorage.getItem('my_growth_know');
    const loadedCounts = localStorage.getItem('my_growth_counts');

    setLogs(loadedLogs ? JSON.parse(loadedLogs) : INITIAL_LOGS);
    setKnowledge(loadedKnow ? JSON.parse(loadedKnow) : INITIAL_KNOWLEDGE);
    setCountdowns(loadedCounts ? JSON.parse(loadedCounts) : INITIAL_COUNTDOWNS);

    if (loadedGoals) {
        let parsed = JSON.parse(loadedGoals);
        if (parsed.length > 0 && parsed[0].subTasks) {
             console.log("Detected old data format, migrating...");
             if(!parsed[0].parentId && parsed[0].parentId !== null) {
                 setGoals(INITIAL_GOALS); 
             } else {
                 setGoals(parsed);
             }
        } else {
            setGoals(parsed);
        }
    } else {
        setGoals(INITIAL_GOALS);
    }

    if (sessionStorage.getItem('is_auth') === 'true') {
        setIsAuthenticated(true);
    }
  }, []);

  // Save Data
  useEffect(() => { if (isAuthenticated) localStorage.setItem('my_growth_logs', JSON.stringify(logs)); }, [logs, isAuthenticated]);
  useEffect(() => { if (isAuthenticated) localStorage.setItem('my_growth_goals', JSON.stringify(goals)); }, [goals, isAuthenticated]);
  
  // Save Knowledge with Error Handling for Quota
  useEffect(() => { 
      if (isAuthenticated) {
          try {
              localStorage.setItem('my_growth_know', JSON.stringify(knowledge)); 
          } catch (e) {
              alert("保存失败：存储空间已满。请尝试删除一些大文件或旧数据。");
          }
      } 
  }, [knowledge, isAuthenticated]);
  
  useEffect(() => { if (isAuthenticated) localStorage.setItem('my_growth_counts', JSON.stringify(countdowns)); }, [countdowns, isAuthenticated]);

  const handleLogin = (e: React.FormEvent) => {
    e.preventDefault();
    if (passwordInput === 'gaomin11') {
      setIsAuthenticated(true);
      sessionStorage.setItem('is_auth', 'true');
    } else {
      alert('密码错误');
    }
  };

  const handleLogout = () => {
      setIsAuthenticated(false);
      sessionStorage.removeItem('is_auth');
      setPasswordInput('');
  }

  // Export Data Function
  const handleExportData = () => {
      const data = {
          logs,
          goals,
          knowledge,
          countdowns,
          version: 1,
          exportDate: new Date().toISOString()
      };
      const blob = new Blob([JSON.stringify(data, null, 2)], { type: 'application/json' });
      const url = URL.createObjectURL(blob);
      const a = document.createElement('a');
      a.href = url;
      a.download = `growth_backup_${new Date().toISOString().split('T')[0]}.json`;
      document.body.appendChild(a);
      a.click();
      document.body.removeChild(a);
      URL.revokeObjectURL(url);
  }

  // Import Data Function
  const handleImportData = (e: React.ChangeEvent<HTMLInputElement>) => {
      const file = e.target.files?.[0];
      if (!file) return;

      const reader = new FileReader();
      reader.onload = (event) => {
          try {
              const data = JSON.parse(event.target?.result as string);
              if (confirm('警告：导入数据将完全覆盖您当前的所有记录！\n\n确定要继续吗？')) {
                  if(data.logs) setLogs(data.logs);
                  if(data.goals) setGoals(data.goals);
                  if(data.knowledge) setKnowledge(data.knowledge);
                  if(data.countdowns) setCountdowns(data.countdowns);
                  alert('数据导入恢复成功！');
                  setIsDataModalOpen(false);
              }
          } catch (err) {
              alert('导入失败：文件格式不正确。');
          }
      };
      reader.readAsText(file);
      // Reset input
      e.target.value = '';
  }

  // --- Render Login ---
  if (!isAuthenticated) {
    return (
      <div className="min-h-screen bg-slate-50 flex flex-col items-center justify-center p-4">
        <div className="w-full max-w-md bg-white rounded-2xl shadow-xl p-8 border border-slate-100">
          <div className="flex justify-center mb-6">
            <div className="bg-slate-800 text-white p-3 rounded-lg">
                <BookOpen size={32} />
            </div>
          </div>
          <h1 className="text-2xl font-bold text-center text-slate-800 mb-2">个人成长空间</h1>
          <p className="text-center text-slate-500 mb-8">私有 • 专注 • 积累</p>
          <form onSubmit={handleLogin} className="space-y-4">
            <div>
              <input
                type="password"
                placeholder="访问密码"
                className="w-full px-4 py-3 border border-slate-200 rounded-lg focus:outline-none focus:ring-2 focus:ring-slate-800 transition-all"
                value={passwordInput}
                onChange={(e) => setPasswordInput(e.target.value)}
              />
            </div>
            <button
              type="submit"
              className="w-full bg-slate-800 text-white py-3 rounded-lg font-medium hover:bg-slate-700 transition-colors"
            >
              进入空间
            </button>
          </form>
        </div>
      </div>
    );
  }

  // --- Render Main App ---
  const NavItem = ({ id, icon: Icon, label }: any) => (
    <button
      onClick={() => { setActiveTab(id); setIsMobileMenuOpen(false); }}
      className={`w-full flex items-center gap-3 px-4 py-3 rounded-lg transition-colors ${
        activeTab === id ? 'bg-slate-800 text-white shadow-md' : 'text-slate-500 hover:bg-slate-100'
      }`}
    >
      <Icon size={20} />
      <span className="font-medium">{label}</span>
    </button>
  );

  return (
    <div className="flex min-h-screen bg-[#f8fafc]">
      {/* Data Management Modal */}
      {isDataModalOpen && (
          <div className="fixed inset-0 z-[60] flex items-center justify-center bg-black/20 backdrop-blur-sm p-4">
             <Card className="w-full max-w-sm animate-in zoom-in-95 duration-200">
                 <div className="flex justify-between items-center mb-6">
                     <h3 className="font-bold text-lg text-slate-800 flex items-center">
                         <Database size={20} className="mr-2 text-slate-500"/> 
                         数据备份与管理
                     </h3>
                     <button onClick={() => setIsDataModalOpen(false)}><X size={20} className="text-slate-400"/></button>
                 </div>
                 
                 <div className="space-y-4">
                     <div className="bg-blue-50 p-4 rounded-lg border border-blue-100">
                         <div className="flex items-center gap-3 mb-2">
                             <div className="bg-white p-2 rounded-full text-blue-600 shadow-sm"><Download size={18}/></div>
                             <div className="font-bold text-slate-700">导出备份</div>
                         </div>
                         <p className="text-xs text-slate-500 mb-3">下载包含所有日记、目标、倒计时和文件资源的 JSON 备份文件。</p>
                         <Button size="sm" onClick={handleExportData} className="w-full">立即导出数据</Button>
                     </div>

                     <div className="bg-slate-50 p-4 rounded-lg border border-slate-100">
                         <div className="flex items-center gap-3 mb-2">
                             <div className="bg-white p-2 rounded-full text-slate-600 shadow-sm"><Upload size={18}/></div>
                             <div className="font-bold text-slate-700">恢复数据</div>
                         </div>
                         <p className="text-xs text-slate-500 mb-3">上传之前的备份文件以恢复所有数据（将覆盖当前数据）。</p>
                         <label className="block w-full text-center bg-white border border-slate-300 text-slate-700 py-2 rounded-lg text-sm font-medium hover:bg-slate-50 cursor-pointer transition-colors">
                            选择备份文件
                            <input type="file" className="hidden" accept=".json" onChange={handleImportData}/>
                         </label>
                     </div>
                 </div>
             </Card>
          </div>
      )}

      {/* Mobile Menu Button */}
      <div className="lg:hidden fixed top-4 right-4 z-50">
          <button onClick={() => setIsMobileMenuOpen(!isMobileMenuOpen)} className="p-2 bg-white rounded-full shadow-lg border border-slate-100 text-slate-700">
             {isMobileMenuOpen ? <X size={24}/> : <Menu size={24}/>}
          </button>
      </div>

      {/* Sidebar */}
      <aside className={`fixed lg:static inset-y-0 left-0 z-40 w-64 bg-white border-r border-slate-200 transform transition-transform duration-300 lg:translate-x-0 ${isMobileMenuOpen ? 'translate-x-0' : '-translate-x-full'}`}>
        <div className="h-full flex flex-col p-6">
          <div className="flex items-center gap-3 mb-10 px-2">
            <div className="bg-slate-800 text-white p-2 rounded-lg">
                <BookOpen size={20} />
            </div>
            <span className="text-xl font-bold text-slate-800 tracking-tight">Growth Space</span>
          </div>

          <nav className="space-y-2 flex-1">
            <NavItem id="dashboard" icon={LayoutDashboard} label="概览" />
            <NavItem id="logs" icon={Calendar} label="每日日记" />
            <NavItem id="goals" icon={Target} label="目标管理" />
            <NavItem id="knowledge" icon={Folder} label="知识库" />
          </nav>

          <div className="pt-6 border-t border-slate-100 space-y-2">
             <button onClick={() => setIsDataModalOpen(true)} className="flex items-center gap-2 text-slate-500 hover:text-slate-800 px-4 py-2 transition-colors text-sm w-full rounded-lg hover:bg-slate-50">
                <Settings size={16} /> 数据管理
             </button>
             <button onClick={handleLogout} className="flex items-center gap-2 text-slate-400 hover:text-red-500 px-4 py-2 transition-colors text-sm w-full rounded-lg hover:bg-red-50">
                <LogOut size={16} /> 退出登录
             </button>
          </div>
        </div>
      </aside>

      {/* Main Content */}
      <main className="flex-1 overflow-y-auto h-screen">
        <div className="max-w-6xl mx-auto p-6 lg:p-12 pb-24">
          {activeTab === 'dashboard' && (
              <Dashboard 
                  logs={logs} 
                  goals={goals} 
                  countdowns={countdowns} 
                  setGoals={setGoals} 
                  setCountdowns={setCountdowns}
                  onNavigateToGoal={(id) => {
                      setCurrentParentId(id);
                      setActiveTab('goals');
                  }}
              />
          )}
          {activeTab === 'logs' && <DiaryModule logs={logs} setLogs={setLogs} />}
          {activeTab === 'goals' && (
              <GoalsModule 
                  goals={goals} 
                  setGoals={setGoals} 
                  currentParentId={currentParentId}
                  setCurrentParentId={setCurrentParentId}
              />
          )}
          {activeTab === 'knowledge' && <KnowledgeModule knowledge={knowledge} setKnowledge={setKnowledge} />}
        </div>
      </main>
    </div>
  );
};

const root = createRoot(document.getElementById('root')!);
root.render(<App />);